package com.example.toycarcontroller

import android.annotation.SuppressLint
import android.bluetooth.*
import android.bluetooth.le.BluetoothLeScanner
import android.bluetooth.le.ScanCallback
import android.bluetooth.le.ScanResult
import android.bluetooth.le.ScanSettings
import android.content.Context
import android.util.Log
import java.util.*
import android.app.Activity
import android.Manifest
import android.bluetooth.le.*
import android.os.Handler
import android.os.Looper
import android.os.Build
import android.content.pm.PackageManager
import androidx.core.content.ContextCompat
import android.widget.Toast


/**
 * 蓝牙服务模块，封装蓝牙设备连接和服务发现功能
 */
class BluetoothService private constructor(private val context: Context) {
    private val TAG = "BluetoothService"
    private lateinit var bluetoothManager: BluetoothManager
    private lateinit var bluetoothAdapter: BluetoothAdapter
    private lateinit var bluetoothLeScanner: BluetoothLeScanner
    private var bluetoothGatt: BluetoothGatt? = null
    private var serviceDiscoveryCallback: ((List<BluetoothGattService>) -> Unit)? = null
    private var connectionStateCallback: ((Boolean, String) -> Unit)? = null
    private val discoveredServices = mutableListOf<BluetoothGattService>()
    private val connectionTimeoutHandler = Handler(Looper.getMainLooper())
    private val scannedDevices = mutableListOf<BluetoothDevice>() // 新增:存储扫描到的设备列表
    private val scanTimeoutHandler = Handler(Looper.getMainLooper()) // 新增:扫描超时Handler
    private val SCAN_PERIOD = 10000L // 新增:扫描超时时间10秒

    // 新增扫描回调
    private var scanCallback: ScanCallback? = null
    private var scanning = false
    private var scanResultCallback: ((BluetoothDevice?, Int) -> Unit)? = null  

    // 添加公开的scanning属性访问方法
    val isScanning: Boolean
        get() = scanning

    // 添加isConnected属性
    var isConnected = false
    private set
    fun getServices(): List<BluetoothGattService> = discoveredServices

    // 添加获取已连接设备名称的方法
    @SuppressLint("MissingPermission")
    fun getConnectedDeviceName(): String {
        return bluetoothGatt?.device?.name ?: "无"
    }

    companion object {
        @Volatile private var instance: BluetoothService? = null
        private const val CONNECTION_TIMEOUT = 10000L
    
        fun getInstance(context: Context): BluetoothService {
            return instance ?: synchronized(this) {
                // 确保使用Application上下文
                val appContext = context.applicationContext
                instance ?: BluetoothService(appContext).also { 
                    instance = it
                    it.initialize()  // 初始化
                }
            }
        }
    }
    
    @SuppressLint("MissingPermission")
    private fun initialize() {
        bluetoothManager = context.getSystemService(Context.BLUETOOTH_SERVICE) as BluetoothManager
        bluetoothAdapter = bluetoothManager.adapter
        // 添加蓝牙适配器状态检查
        if (bluetoothAdapter == null || !bluetoothAdapter.isEnabled) {
            Log.e(TAG, "蓝牙适配器不可用或未启用")
            return
        }
        bluetoothLeScanner = bluetoothAdapter.bluetoothLeScanner
    }

    /**
     * 开始扫描蓝牙设备
     * @param callback 扫描结果回调
     */
    @SuppressLint("MissingPermission")
    fun startScan(callback: (BluetoothDevice?, Int) -> Unit) {
        // 存储回调
        scanResultCallback = callback

        if (Looper.myLooper() != Looper.getMainLooper()) {
            Handler(Looper.getMainLooper()).post {
                startScan(callback)
            }
            return
        }

        if (!checkPermissions()) {
            Log.e(TAG, "缺少必要的蓝牙权限")
            Handler(Looper.getMainLooper()).post {
                Toast.makeText(context, "缺少蓝牙权限，请授予权限后重试", Toast.LENGTH_SHORT).show()
                // 修改：不再返回无效设备，直接返回错误状态
                callback.invoke(null, -1)
            }
            return
        }

        // 使用新线程执行扫描操作
        Thread {
            try {
                // 同步块防止并发扫描
                synchronized(this) {
                    stopScan()
                    scanTimeoutHandler.removeCallbacksAndMessages(null)

                    scanCallback = object : ScanCallback() {
                        override fun onScanResult(callbackType: Int, result: ScanResult) {
                            super.onScanResult(callbackType, result)
                            scanResultCallback?.invoke(result.device, result.rssi)
                        }
                        
                        override fun onScanFailed(errorCode: Int) {
                            Log.e(TAG, "扫描失败: $errorCode")
                            stopScan()
                            Handler(Looper.getMainLooper()).post {
                                Toast.makeText(context, "扫描失败: $errorCode", Toast.LENGTH_SHORT).show()
                            }
                        }
                    }
                    
                    bluetoothLeScanner.startScan(null, 
                        ScanSettings.Builder()
                            .setScanMode(ScanSettings.SCAN_MODE_LOW_LATENCY)
                            .build(), 
                        scanCallback)
                    
                    scanTimeoutHandler.postDelayed({
                        stopScan()
                        Log.d(TAG, "扫描超时自动停止")
                    }, SCAN_PERIOD)
                    scanning = true
                }
            } catch (e: Exception) {
                Log.e(TAG, "扫描启动失败: ${e.message}")
                stopScan()
            }
        }.start()
    }

    @SuppressLint("MissingPermission")
    fun stopScan() {
        if (!scanning) return

        try {
            scanCallback?.let { 
                if (checkPermissions()) {
                    bluetoothLeScanner.stopScan(it)
                    Log.d(TAG, "成功停止扫描")
                } else {
                    Log.w(TAG, "无权限停止扫描")
                }
            }
        } catch (e: IllegalStateException) {
            Log.e(TAG, "蓝牙适配器状态异常: ${e.message}")
        } catch (e: SecurityException) {
            Log.e(TAG, "停止扫描权限异常: ${e.message}")
        } catch (e: Exception) {
            Log.e(TAG, "停止扫描时出错: ${e.message}")
        } finally {
            scanning = false
            scanCallback = null
            scanTimeoutHandler.removeCallbacksAndMessages(null)
            // 修改：扫描停止后返回null设备
            Handler(Looper.getMainLooper()).post {
                scanResultCallback?.invoke(null, -2)
            }
        }
    }
    
    
    /**
     * 连接蓝牙设备
     * @param device 要连接的蓝牙设备
     * @param onConnected 连接成功回调
     * @param onDisconnected 连接断开回调
     */
    @SuppressLint("MissingPermission")
    fun connectToDevice(device: BluetoothDevice) {
        bluetoothGatt?.close()
        bluetoothGatt = device.connectGatt(
            context,
            false,
            object : BluetoothGattCallback() {
                override fun onConnectionStateChange(gatt: BluetoothGatt, status: Int, newState: Int) {
                    when (newState) {
                        BluetoothProfile.STATE_CONNECTED -> {
                            Log.d(TAG, "已连接，开始发现服务...")
                            isConnected = true  // 设置连接状态
                            val deviceName = gatt.device.name ?: gatt.device.address
                            connectionStateCallback?.invoke(true, deviceName)
                            gatt.discoverServices()
                        }
                        BluetoothProfile.STATE_DISCONNECTED -> {
                            Log.w(TAG, "已断开连接")
                            isConnected = false  // 设置断开状态
                            connectionStateCallback?.invoke(false, "")
                        }
                    }
                }

                override fun onServicesDiscovered(gatt: BluetoothGatt, status: Int) {
                    if (status == BluetoothGatt.GATT_SUCCESS) {
                        Log.d(TAG, "发现服务成功")
                        discoveredServices.clear()
                        discoveredServices.addAll(gatt.services)
                        val services = gatt.services
                        serviceDiscoveryCallback?.invoke(services)
                    } else {
                        Log.e(TAG, "服务发现失败: $status")
                    }
                }
            },
            BluetoothDevice.TRANSPORT_LE
        )
        // 添加超时处理
        connectionTimeoutHandler.postDelayed({
            if (!isConnected) {
                disconnect()
                connectionStateCallback?.invoke(false, "连接超时")
            }
        }, CONNECTION_TIMEOUT)
    }

    /**
     * 设置服务发现回调
     * @param callback 发现服务后的回调函数，可为null
     */
    fun setServiceDiscoveryCallback(callback: ((List<BluetoothGattService>) -> Unit)?) {
        serviceDiscoveryCallback = callback
    }

    /**
     * 设置连接状态回调
     * @param callback 连接状态变化回调，可为null
     */
    fun setConnectionStateCallback(callback: ((Boolean, String) -> Unit)?) {
        connectionStateCallback = callback
    }

    // BluetoothService.kt 新增
    @SuppressLint("MissingPermission")
    fun writeCharacteristic(
        serviceUuid: UUID,
        characteristicUuid: UUID,
        data: ByteArray
    ): Boolean {
        val service = bluetoothGatt?.getService(serviceUuid) ?: return false
        val characteristic = service.getCharacteristic(characteristicUuid) ?: return false
        characteristic.value = data
        return bluetoothGatt?.writeCharacteristic(characteristic) ?: false
    }
    /**
     * 断开蓝牙连接
     */
    @SuppressLint("MissingPermission")
    fun disconnect() {
        bluetoothGatt?.disconnect()
        bluetoothGatt?.close()
        bluetoothGatt = null
        isConnected = false  // 设置断开状态
    }
    
    // 新增权限检查方法
    private fun checkPermissions(): Boolean {
        val requiredPermissions = if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.S) {
            arrayOf(
                Manifest.permission.BLUETOOTH_SCAN,
                Manifest.permission.BLUETOOTH_CONNECT,
                Manifest.permission.ACCESS_FINE_LOCATION
            )
        } else {
            arrayOf(
                Manifest.permission.ACCESS_FINE_LOCATION
            )
        }
        
        return requiredPermissions.all { 
            ContextCompat.checkSelfPermission(context, it) == PackageManager.PERMISSION_GRANTED 
        }.also { hasPermission ->
            if (!hasPermission) {
                Log.e(TAG, "缺少以下权限: ${requiredPermissions.filter { 
                    ContextCompat.checkSelfPermission(context, it) != PackageManager.PERMISSION_GRANTED 
                }}")
            }
        }
    }
    
    // 在原有代码基础上修改扫描相关逻辑
    fun startBleScan(
        context: Context,
        scanCallback: ScanCallback,
        onDeviceFound: (device: BluetoothDevice) -> Unit
    ) {
        Log.d(TAG, "开始准备蓝牙扫描流程...")
        
        // 确保蓝牙适配器可用
        val bluetoothAdapter = BluetoothAdapter.getDefaultAdapter()
        if (bluetoothAdapter == null || !bluetoothAdapter.isEnabled) {
            Log.e(TAG, "蓝牙不可用或未启用")
            return
        }

        try {
            Log.d(TAG, "创建蓝牙扫描器实例")
            val scanner = bluetoothAdapter.bluetoothLeScanner
            if (scanner == null) {
                Log.e(TAG, "无法获取蓝牙扫描器实例")
                return
            }

            // 清除之前的扫描结果
            scannedDevices.clear()
            
            // 设置扫描参数
            val settings = ScanSettings.Builder()
                .setScanMode(ScanSettings.SCAN_MODE_LOW_LATENCY)
                .setCallbackType(ScanSettings.CALLBACK_TYPE_ALL_MATCHES)
                .build()
            
            val filters = mutableListOf<ScanFilter>()
            
            Log.d(TAG, "开始执行蓝牙扫描")
            scanner.startScan(filters, settings, scanCallback)
            
            // 设置扫描超时
            scanTimeoutHandler.postDelayed({
                Log.d(TAG, "扫描超时，自动停止扫描")
                stopBleScan(scanner, scanCallback)
            }, SCAN_PERIOD)
            
        } catch (e: SecurityException) {
            Log.e(TAG, "蓝牙扫描权限异常: ${e.message}")
        } catch (e: IllegalStateException) {
            Log.e(TAG, "蓝牙扫描状态异常: ${e.message}")
        }
    }

    fun stopBleScan(scanner: BluetoothLeScanner?, scanCallback: ScanCallback) {
        try {
            if (!checkPermissions()) {
                Log.e(TAG, "缺少蓝牙扫描权限，无法停止扫描")
                return
            }
            Log.d(TAG, "尝试停止蓝牙扫描")
            scanner?.stopScan(scanCallback)
            scanTimeoutHandler.removeCallbacksAndMessages(null)
            Log.d(TAG, "蓝牙扫描已停止")
        } catch (e: SecurityException) {
            Log.e(TAG, "停止扫描权限异常: ${e.message}")
        } catch (e: Exception) {
            Log.e(TAG, "停止扫描时出错: ${e.message}")
        }
    }

    // 新增扫描回调设置方法
    fun setScanCallback(callback: ScanCallback?) {
        // 这里可以添加额外的验证或处理逻辑
        this.scanCallback = callback
    }
}
